﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using GMAC.ReportingSystem.Business.Entities;
using FrameworkManapro.BusinessModel;
using Excel = Microsoft.Office.Interop.Excel;
using System.Runtime.InteropServices;
using GMAC.ReportingSystem.Business.Entities.Configuration;
//using System.Data;

namespace GMAC.ReportingSystem.Business.Components
{
    public class LaoSalvageAccountsComponent : IBusinessComponent<LaoSalvageAccount>
    {
        // Referencia la clase de datos
        private DataAccess.LaoSalvageAccountsAccess dac;

        // Constructor que instancia la capa de datos
        #region Constructor
            /// <summary>
            /// Constructor de la la clase de negocios que crea una instancia de la clase de datos
            /// </summary>
            public LaoSalvageAccountsComponent()
            {
                dac = new DataAccess.LaoSalvageAccountsAccess();
            } // LaoSalvageAccountsComponent
        #endregion

        // Metodos no Implementados pide que pide "IBusinessComponent"
        #region IBusinessComponent<LaoSalvageAccount> Members

            /// <summary>
            /// Metodo no implementado
            /// </summary>
            /// <param name="entityToCreate"></param>
            /// <returns></returns>
            public int Create(LaoSalvageAccount entityToCreate)
            {
                throw new NotImplementedException();
            } // Create

            /// <summary>
            /// Metodo no implementado
            /// </summary>
            /// <param name="entityToDelete"></param>
            /// <returns></returns>
            public int Delete(LaoSalvageAccount entityToDelete)
            {
                throw new NotImplementedException();
            } // Delete

            /// <summary>
            /// Metodo no implementado
            /// </summary>
            /// <param name="entityToEdit"></param>
            /// <returns></returns>
            public int Edit(LaoSalvageAccount entityToEdit)
            {
                throw new NotImplementedException();
            } // Edit

            /// <summary>
            /// Metodo no implementado
            /// </summary>
            /// <param name="entityId"></param>
            /// <returns></returns>
            public LaoSalvageAccount GetDetails(object entityId)
            {
                throw new NotImplementedException();
            } // GetDetails

        #endregion



            /// <summary>
            /// Carga el archivo "LAO SAlvage - Regional Extract" que contiene las cuentas con estatus PERDIDA
            /// </summary>
            /// <remarks>El archivo es de tipo Excel</remarks>
            /// <param name="processDate">Fecha en la que se esta procesando el archivo</param>
            /// <param name="fileName">Ruta y nombre del archivo a procesar</param>
            /// <param name="UserId">Usuari oquer ejecuta la operacion</param>
            /// <param name="LAOInvalids">Lista de los registros invalidos que se encontraron en el archivo</param>
            /// <param name="LAOValids">Lista de los registros validos que se encontraron en el archivo</param>
            public void LoadFile(DateTime processDate, string fileName, int UserId, ref StringLaoSalvageAccountCollection LAOInvalids, ref StringLaoSalvageAccountCollection LAOValids)
            {
            // Primera fila de los datos en el archivo
            int FIRST_ROW = 2;

            StringLaoSalvageAccountCollection LAORecords = new StringLaoSalvageAccountCollection();
            
            //  asigna las columnas donde se encuentran los datos en el archivo excel
            string COL_1_ACCOUNTNUMBER	        = "C";
            string COL_2_ACCOUNTSTATUSCODE      = "D";
            string COL_3_ACCOUNTSTATUSDATE      = "E";
            string COL_4_DEALERNAME             = "CJ";
            string COL_5_DEALERNUMBER           = "CK";
            string COL_6_THIRDPARTYNAME         = "FR";
            string COL_7_THIRDPARTYTYPECODE     = "FS";
            string COL_8_CURRENTTOTALAMOUNT     = "BK";

            var oldCI = System.Threading.Thread.CurrentThread.CurrentCulture;
            System.Threading.Thread.CurrentThread.CurrentCulture = new System.Globalization.CultureInfo("en-US");
            var app = new Excel.Application();
            Excel.Workbook wb = null;
            var missing = Type.Missing;
            StringLaoSalvageAccount LAORecord;
                


            try
            {
                string strCulture = System.Configuration.ConfigurationManager.AppSettings["Culture"];
                System.Globalization.CultureInfo infCulture = new System.Globalization.CultureInfo(strCulture);

                wb = app.Workbooks.Open(fileName, missing, true, missing, missing,
                    missing, true, missing, missing, missing, false,
                    missing, false, true, false);
                var sheet = wb.Sheets[1] as Excel.Worksheet;
                if (sheet != null)
                {
                    //lastRow = sheet.UsedRange.EntireRow.Count;
                    int i = FIRST_ROW;

                    // Formatea las letras de las columnas en el excel de las que proviene los valores
                    var cell1_ACCOUNTNUMBER         = string.Format("{0}{1}", COL_1_ACCOUNTNUMBER, i);
                    var cell2_ACCOUNTSTATUSCODE     = string.Format("{0}{1}", COL_2_ACCOUNTSTATUSCODE, i);
                    var cell3_ACCOUNTSTATUSDATE     = string.Format("{0}{1}", COL_3_ACCOUNTSTATUSDATE, i);
                    var cell4_DEALERNAME            = string.Format("{0}{1}", COL_4_DEALERNAME, i);
                    var cell5_DEALERNUMBER          = string.Format("{0}{1}", COL_5_DEALERNUMBER, i);
                    var cell6_THIRDPARTYNAME        = string.Format("{0}{1}", COL_6_THIRDPARTYNAME, i);
                    var cell7_THIRDPARTYTYPECODE    = string.Format("{0}{1}", COL_7_THIRDPARTYTYPECODE, i);
                    var cell8_CURRENTTOTALAMOUNT    = string.Format("{0}{1}", COL_8_CURRENTTOTALAMOUNT, i);

                    // declare las variables donde se capturaran los valores de cada filas del excel
                    string str_cell1_ACCOUNTNUMBER      = sheet.get_Range(cell1_ACCOUNTNUMBER, cell1_ACCOUNTNUMBER).Text.ToString().Trim();
                    string str_cell2_ACCOUNTSTATUSCODE  = sheet.get_Range(cell2_ACCOUNTSTATUSCODE, cell2_ACCOUNTSTATUSCODE).Text.ToString().Trim();
                    string str_cell3_ACCOUNTSTATUSDATE  = sheet.get_Range(cell3_ACCOUNTSTATUSDATE, cell3_ACCOUNTSTATUSDATE).Text.ToString().Trim();
                    string str_cell4_DEALERNAME         = sheet.get_Range(cell4_DEALERNAME, cell4_DEALERNAME).Text.ToString().Trim();
                    string str_cell5_DEALERNUMBER       = sheet.get_Range(cell5_DEALERNUMBER, cell5_DEALERNUMBER).Text.ToString().Trim();
                    string str_cell6_THIRDPARTYNAME     = sheet.get_Range(cell6_THIRDPARTYNAME, cell6_THIRDPARTYNAME).Text.ToString().Trim();
                    string str_cell7_THIRDPARTYTYPECODE = sheet.get_Range(cell7_THIRDPARTYTYPECODE, cell7_THIRDPARTYTYPECODE).Text.ToString().Trim();
                    string str_cell8_CURRENTTOTALAMOUNT = sheet.get_Range(cell8_CURRENTTOTALAMOUNT, cell8_CURRENTTOTALAMOUNT).Text.ToString().Trim();

                    // Se hara el while mientras exista por lo menos un campo con longitudes > 0
                    while (   str_cell1_ACCOUNTNUMBER.Length         > 0 
                           || str_cell2_ACCOUNTSTATUSCODE.Length     > 0 
                           || str_cell3_ACCOUNTSTATUSDATE.Length     > 0
                           || str_cell4_DEALERNAME.Length            > 0
                           || str_cell5_DEALERNUMBER.Length          > 0
                           || str_cell6_THIRDPARTYNAME.Length        > 0
                           || str_cell7_THIRDPARTYTYPECODE.Length    > 0
                           || str_cell8_CURRENTTOTALAMOUNT.Length    > 0
                          ) // while
                    {
                        // Inicializa la cadena que captura las razones de rechazo
                        //strRejectionReason = "";

                        // Instancia los objetos para capturar una fila de el archivo e insertarlos en la coleccion de los validos o los invalidos
                        LAORecord = new StringLaoSalvageAccount();

                        LAORecord.LoadDate              = processDate;
                        LAORecord.AccountNumber         = str_cell1_ACCOUNTNUMBER;
                        LAORecord.AccountStatusCode     = str_cell2_ACCOUNTSTATUSCODE;
                        LAORecord.AccountStatusDate     = str_cell3_ACCOUNTSTATUSDATE; //DateTime.Parse(str_cell3_ACCOUNTSTATUSDATE, infCulture);
                        LAORecord.DealerName            = str_cell4_DEALERNAME;
                        LAORecord.DealerNumber          = str_cell5_DEALERNUMBER;
                        LAORecord.ThirdPartyName        = str_cell6_THIRDPARTYNAME;
                        LAORecord.ThirdPartyTypeCode    = str_cell7_THIRDPARTYTYPECODE;
                        LAORecord.CurrentTotalAmount    = str_cell8_CURRENTTOTALAMOUNT; //decimal.Parse(str_cell8_CURRENTTOTALAMOUNT);

                        // Agrega el Item a la coleccion
                        LAORecords.Add(LAORecord);

                     // Se mueve al siguiente registro del while
                    i++;

                    // Formatea las letras de las columnas en el excel de las que proviene los valores
                    cell1_ACCOUNTNUMBER         = string.Format("{0}{1}", COL_1_ACCOUNTNUMBER, i);
                    cell2_ACCOUNTSTATUSCODE     = string.Format("{0}{1}", COL_2_ACCOUNTSTATUSCODE, i);
                    cell3_ACCOUNTSTATUSDATE     = string.Format("{0}{1}", COL_3_ACCOUNTSTATUSDATE, i);
                    cell4_DEALERNAME            = string.Format("{0}{1}", COL_4_DEALERNAME, i);
                    cell5_DEALERNUMBER          = string.Format("{0}{1}", COL_5_DEALERNUMBER, i);
                    cell6_THIRDPARTYNAME        = string.Format("{0}{1}", COL_6_THIRDPARTYNAME, i);
                    cell7_THIRDPARTYTYPECODE    = string.Format("{0}{1}", COL_7_THIRDPARTYTYPECODE, i);
                    cell8_CURRENTTOTALAMOUNT    = string.Format("{0}{1}", COL_8_CURRENTTOTALAMOUNT, i);

                    // vuelve a capturar los valores de la siguiente fila del excel para el while
                    str_cell1_ACCOUNTNUMBER         = sheet.get_Range(cell1_ACCOUNTNUMBER, cell1_ACCOUNTNUMBER).Text.ToString().Trim();
                    str_cell2_ACCOUNTSTATUSCODE     = sheet.get_Range(cell2_ACCOUNTSTATUSCODE, cell2_ACCOUNTSTATUSCODE).Text.ToString().Trim();
                    str_cell3_ACCOUNTSTATUSDATE     = sheet.get_Range(cell3_ACCOUNTSTATUSDATE, cell3_ACCOUNTSTATUSDATE).Text.ToString().Trim();
                    str_cell4_DEALERNAME            = sheet.get_Range(cell4_DEALERNAME, cell4_DEALERNAME).Text.ToString().Trim();
                    str_cell5_DEALERNUMBER          = sheet.get_Range(cell5_DEALERNUMBER, cell5_DEALERNUMBER).Text.ToString().Trim();
                    str_cell6_THIRDPARTYNAME        = sheet.get_Range(cell6_THIRDPARTYNAME, cell6_THIRDPARTYNAME).Text.ToString().Trim();
                    str_cell7_THIRDPARTYTYPECODE    = sheet.get_Range(cell7_THIRDPARTYTYPECODE, cell7_THIRDPARTYTYPECODE).Text.ToString().Trim();
                    str_cell8_CURRENTTOTALAMOUNT    = sheet.get_Range(cell8_CURRENTTOTALAMOUNT, cell8_CURRENTTOTALAMOUNT).Text.ToString().Trim();

                    } // while
                    
                    dac.UploadLoanFile(processDate, UserId, LAORecords, ref LAOInvalids, ref LAOValids);
                } // if (sheet != null)
                else
                {
                    throw new ApplicationException("File invalid.");
                }
            } // try
            catch
            {
                throw;
            } // catch
            finally
            {
                if (wb != null)
                {
                    wb.Close(false, missing, missing);
                    Marshal.FinalReleaseComObject(wb);
                } // if
                if (true)
                {
                    app.Quit();
                    Marshal.FinalReleaseComObject(app);
                } // if
                GC.Collect();
                GC.WaitForPendingFinalizers();
                GC.Collect();
                GC.WaitForPendingFinalizers();
                System.Threading.Thread.CurrentThread.CurrentCulture = oldCI;

            } // finally
        } // LoadFile


        /// <summary>
        /// Metodo que inserta los registros valios del archivo excel
        /// </summary>
        /// <param name="typeFile">Tipo de archivo</param>
        /// <param name="UserId">Usuario que procesa el archivo</param>
        public void GenerateUploadFile(int UserId)
        {
            dac.GenerateUploadFile(UserId);
        } // GenerateUploadFile

        /// <summary>
        /// Recibe una coleccion y la retorna ordenada segun indiquen los parametros
        /// </summary>
        /// <param name="records">Coleccion de valores a ordenar</param>
        /// <param name="column">Campo por el que va a ordenar</param>
        /// <param name="order">"ASC" o "DESC"</param>
        /// <returns>Lista ordenada</returns>
        public StringLaoSalvageAccountCollection sord(StringLaoSalvageAccountCollection records, string column, string order)
        {
            return dac.sord(records, column, order);
        } // sord

        /// <summary>
        /// Valida si los datos son numericos
        /// </summary>
        /// <param name="value">Valor a validar</param>
        /// <returns>
        /// true: Es Valido
        /// false: No es Valido
        /// </returns>
        public bool IsNumeric(string value)
        {
            try
            {
                long.Parse(value);
                return true;
            }
            catch (Exception)
            {
                return false;
            }
        } // IsNumeric

        /// <summary>
        /// Valida si los datos son Decimales
        /// </summary>
        /// <param name="value">Valor a validar</param>
        /// <returns>
        /// true: Es Valido
        /// false: No es Valido
        /// </returns>
        public bool IsDecimal(string value)
        {
            try
            {
                decimal.Parse(value);
                return true;
            }
            catch (Exception)
            {
                return false;
            }
        } // IsDecimal

        /// <summary>
        /// Valida si los datos son Date
        /// </summary>
        /// <param name="value">Valor a validar</param>
        /// <returns>
        /// true: Es Valido
        /// false: No es Valido
        /// </returns>
        public bool IsDate(string value)
        {
            try
            {
                string strCulture = System.Configuration.ConfigurationManager.AppSettings["Culture"];

                DateTime.Parse(value, new System.Globalization.CultureInfo(strCulture));

                return true;
            }
            catch (Exception)
            {
                return false;
            }
        } // IsDate

    } // class
} // namespace
